package com.eastdigit.system.service;

import com.eastdigit.servlet.ReqBean;
import com.eastdigit.system.inter.UserMapper;
import com.eastdigit.system.model.BusinessException;
import com.eastdigit.system.model.IDepartment;
import com.eastdigit.system.model.SqlBuilder;
import com.eastdigit.system.model.User;
import com.eastdigit.util.Encrypt;
import com.eastdigit.util.PropertiesUtil;
import com.eastdigit.util.StringUtil;
import net.sf.json.JSONArray;
import net.sf.json.JSONObject;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service
public class UserService extends BaseService implements IUserService<User>, IFieldAliasService {

    @Autowired
    private UserMapper userMapper;
    @Autowired
    private IDepartmentService departmentService;
    @Autowired
    private UserRoleService userRoleService;
    @Autowired
    private PermissionService permissionService;

    /**
     * 用户登录
     * 
     * @param userId
     * @param deviceType
     * @param deviceToken
     * @return
     */
    @Override
    public JSONObject login(String userId, String deviceType, String deviceToken) {
        User user = userMapper.selectByPrimaryKey(userId);
        if ("0".equals(user.getState())) {
            throw new BusinessException("请等待管理员激活");
        }
        JSONObject json = user.toJSONObject();
        // 设置部门名称
        IDepartment department = departmentService.queryDepartment(user.getDeptId());
        json.put("deptName", department == null ? "" : department.getDeptName());
        // 设置权限
        json.put("permission", permissionService.getUrlPermissionsOfUserForLogin(user.getId()));

        // 某个页面定义了但是没有的权限
        json.put("permissionDeny", permissionService.queryOutOfAuthedPermissionsOfUser(user.getId()));

        json.put("menus", permissionService.queryMenuForLeftBarOfUser(userId));
        return json;
    }

    /**
     * 查询用户(条件，分页)
     * 
     * @param reqBean
     * @return
     */
    @Override
//    @FieldAlias(service = "userService", field = "userId", alias = "userName2")
//    @FieldAliases({ @FieldAlias(service = "userService", field = "userId", alias = "userName3"),
//            @FieldAlias(service = "userService", field = "userId", alias = "userName4") })
    public JSONObject queryTable(ReqBean reqBean) {
        String deptId = reqBean.getInfo("deptId");
        String codeOrName = StringUtils.trimToEmpty(reqBean.getInfo("codeOrName"));

        SqlBuilder sqlBuilder = new SqlBuilder(
                "select USER_ID, USER_CODE, USER_NAME, C_GENDER, TELEPHONE, MOBILE1, MOBILE2, EMAIL, DEPT_ID, SOURCE_ID, C_USER_TYPE,"
                        + " C_USER_STATE, OPERATOR, REMARK, EXTRA1, EXTRA2 from SYS_USER a where a.USER_CODE <> '001' ")
                .addWhereDataScope("a.DEPT_ID", reqBean);
        if (StringUtil.isNotEmpty(deptId)) {
            List<IDepartment> list = departmentService.queryDescendantDepartmentAndSelf(deptId);
            Object[] deptIds = new Object[list.size()];
            for (int i = 0; i < list.size(); i++) {
                deptIds[i] = list.get(i).getDeptId();
            }
            sqlBuilder.addWhereIn("DEPT_ID", deptIds);
        }

        if (StringUtils.isNotBlank(codeOrName)) {
            sqlBuilder.appendSql(" and (USER_CODE = ? or USER_NAME like ?)", codeOrName, "%" + codeOrName + "%");
        }
        sqlBuilder.orderBy(" order by USER_NAME");

        return queryTable(sqlBuilder, reqBean.getPageSize(), reqBean.getPageIndex());
    }

    @Override
    public Map<String, Object> dealFieldAlias(List<Object> fields, String param) {
        JSONArray array = query(new SqlBuilder("select USER_ID, USER_NAME from SYS_USER where 1= 1").addWhereIn(
                "USER_ID", fields));
        Map<String, Object> map = new HashMap<String, Object>();
        for (int i = 0; i < array.size(); i++) {
            JSONObject json = array.getJSONObject(i);
            map.put(json.getString("userId"), json.getString("userName"));
        }
        return map;
    }

    @Override
    public User queryById(String userId) {
        return userMapper.selectByPrimaryKey(userId);
    }

    /**
     * 根据用户编码，获取用户
     * 
     * @param userCode
     * @return
     */
    @Override
    public User queryByCode(String userCode) {
        return userMapper.selectByUserCode(userCode);
    }

    /**
     * 新增用户
     * 
     * @param user
     */
    @Override
    public void add(User user) {
        String userCode = user.getCode();
        if (StringUtil.isEmpty(userCode)) {
            throw new BusinessException("用户编码不能为空！");
        } else if (queryByCode(userCode) != null) {
            throw new BusinessException("用户编码已被使用！");
        }
        user.setId(intIncrementId("SYS_USER", "USER_ID"));
        user.setMakeTime(user.getModifyTime());
        user.setModifyTime(user.getMakeTime());
        try {
            user.setPassword(Encrypt.encodeMD5(PropertiesUtil.getProperty("project.init.password")));
        } catch (Exception e) {
            throw new BusinessException("密码加密失败！");
        }

        userMapper.insert(user);
    }

    /**
     * 修改用户
     * 
     * @param user
     */
    @Override
    public void update(User user) {
        String userId = user.getId();
        if (StringUtil.isEmpty(userId)) {
            throw new BusinessException("获取主键失败");
        }
        String userCode = user.getCode();
        if (StringUtil.isNotEmpty(userCode)) {
            if (this.executeInt("select count(0) from SYS_USER where USER_ID != ? and USER_CODE = ?", userId, userCode) > 0) {
                throw new BusinessException("用户编码已被使用！");
            }
        }
        userMapper.updateByPrimaryKeySelective(user);
    }

    /**
     * 删除用户
     * 
     * @param userId
     */
    @Override
    public void delete(String userId) {
        if (StringUtil.isEmpty(userId)) {
            throw new BusinessException("获取主键失败");
        }
        // 删除角色对应关系
        userRoleService.delUserRoleOfUser(userId);

        userMapper.deleteByPrimaryKey(userId);
    }

    /**
     * 更新用户密码
     * 
     * @param userId
     * @param oldPasword
     * @param newPassword
     */
    @Override
    public void updatePassword(String userId, String oldPasword, String newPassword) {
        User user = userMapper.selectByPrimaryKey(userId);

        if (!user.getPassword().equals(oldPasword)) {
            throw new BusinessException("原密码不正确！");
        }
        if (StringUtil.isEmpty(newPassword) || newPassword.length() < 6) {
            throw new BusinessException("密码长度不能少于6位！");
        }
        try {
            user.setPassword(Encrypt.encodeMD5(newPassword));
        } catch (Exception e) {
            throw new BusinessException("密码加密失败！");
        }
        userMapper.updateByPrimaryKeySelective(user);
    }

    /**
     * 重置密码
     * 
     * @param userId
     */
    @Override
    public void resetPassword(String userId) {
        User user = new User();
        user.setId(userId);
        try {
            user.setPassword(Encrypt.encodeMD5(PropertiesUtil.getProperty("project.init.password")));
        } catch (Exception e) {
            throw new BusinessException("密码加密失败！");
        }
        userMapper.updateByPrimaryKeySelective(user);
    }

    @Override
    public List<User> queryUserOfDept(List<String> deptIds) {
        return userMapper.selectUserOfDepts(deptIds);
    }

    @Override
    public User getUserFromRequest(ReqBean reqBean) {
        User user = new User();
        user.setId(reqBean.getInfo("userId"));
        user.setCode(reqBean.getInfo("userCode"));
        user.setName(reqBean.getInfo("userName"));
        user.setGender(reqBean.getInfo("gender"));
        user.setTelephone(reqBean.getInfo("telephone"));
        user.setMobile1(reqBean.getInfo("mobile1"));
        user.setMobile2(reqBean.getInfo("mobile2"));
        user.setEmail(reqBean.getInfo("email"));
        user.setDeptId(reqBean.getInfo("deptId"));
        // user.setPassword(reqBean.getInfo("password"));
        user.setState(reqBean.getInfo("userState"));
        user.setOperator(reqBean.getUserId());
        // user.setModifyTime(new Date());
        user.setRemark(reqBean.getInfo("remark"));
        user.setType(reqBean.getInfo("userType"));
        user.setExtra1(reqBean.getInfo("extra1"));
        user.setExtra2(reqBean.getInfo("extra2"));
        return user;
    }
}
